package org.tgcloud.group.core.ExportUtils;

import com.alibaba.fastjson.JSONObject;
import com.aliyun.oss.*;
import com.aliyun.oss.common.auth.*;
import com.aliyun.oss.common.comm.SignVersion;
import com.aliyun.oss.model.PutObjectRequest;
import com.aliyun.oss.model.PutObjectResult;
import java.io.ByteArrayInputStream;

import com.aliyuncs.exceptions.ClientException;
import com.google.common.collect.Lists;
import org.apache.poi.ss.usermodel.ClientAnchor;
import org.apache.poi.ss.usermodel.PictureData;
import org.apache.poi.xssf.usermodel.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.tgcloud.group.core.GlobalStatic;
import org.tgcloud.group.core.aliyun.oss.OSSUtils;
import org.tgcloud.group.entity.Media;

import java.io.*;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.stream.Collectors;

/**
 * @Author: zhy
 * @Created: 2025-03-03-下午6:07
 * @Description:
 */
@Component
public class PicUtils {

    @Autowired
    private OSSUtils ossUtils;

    public void extractPictures(String filePath, String fileName) {
        try (FileInputStream fis = new FileInputStream(filePath);
             XSSFWorkbook workbook = new XSSFWorkbook(fis)) {
            Map<String, byte[]> map = new HashMap<>();
            for (int i = 0; i < workbook.getNumberOfSheets(); i++) {
                XSSFSheet sheet = workbook.getSheetAt(i);
                // 获取所有图片和它们的位置信息
                Map<String, PictureData> sheetPictures = getPictures(sheet);
                for (String key : sheetPictures.keySet()){
                    String[] split = key.split(":");
                    String rowNum = split[0];
                    PictureData picture = sheetPictures.get(key);
                    // 获取图片字节流
                    byte[] bytes = picture.getData();
                    // 这里可以将图片保存到文件系统或者进行进一步处理
                    String extension = picture.suggestFileExtension();
                    String imageName = "pic_" + fileName + "_" + rowNum + "." + extension;
                    String url = ExcelUtils.doViewOSSPicPath("pic") + "/" + imageName;
//                    map.put(url, bytes);
                    System.out.println(url);
                    ossUtils.uploadFile(url, bytes);
                }
            }
//            doUpload(map);
        } catch (FileNotFoundException e) {
            throw new RuntimeException(e);
        } catch (IOException e) {
            throw new RuntimeException(e);
        }
    }

    public void doUpload(Map<String, byte[]> map){
        // 对map进行数据分片
        List<String> keyList = new ArrayList<>(map.keySet());
        for (String s : keyList){
            ossUtils.uploadFile(s, map.get(s));
        }
//        int batchSize = 10000;
//        List<List<String>> partitionedData = Lists.partition(keyList, batchSize);
//        ExecutorService executor = Executors.newFixedThreadPool(Runtime.getRuntime().availableProcessors());
//        CountDownLatch latch = new CountDownLatch(partitionedData.size());
//        for (final List<String> chunk : partitionedData) {
//            executor.submit(() -> {
//                try {
//                    chunk.forEach(s -> {
//                        ossUtils.uploadFile(s, map.get(s));
//                    });
//                } catch (Exception e) {
//                    e.printStackTrace();
//                } finally {
//                    latch.countDown();
//                }
//            });
//        }
//        try {
//            latch.await(); // 等待所有任务完成
//        } catch (InterruptedException e) {
//            throw new RuntimeException(e);
//        }
//        executor.shutdown();
    }

    public Map<String, PictureData> getPictures(XSSFSheet sheet) throws IOException {
        Map<String, PictureData> pictures = new HashMap<>();
        // 获取当前sheet的所有绘图对象
        XSSFDrawing drawing = sheet.getDrawingPatriarch();
        if (drawing != null) {
            List<XSSFShape> shapes = drawing.getShapes();
            for (XSSFShape shape : shapes) {
                if (shape instanceof XSSFPicture) {
                    XSSFPicture picture = (XSSFPicture) shape;
                    PictureData img = picture.getPictureData();
                    ClientAnchor anchor = picture.getClientAnchor();
                    // 使用行和列的索引来作为键值
                    String key = anchor.getRow1() + ":" + anchor.getCol1();
                    pictures.put(key, img);
                }
            }
        }
        return pictures;
    }

    /**
     * 将图片字节流保存到指定路径。
     *
     * @param imageBytes 图片的字节数据
     * @param filePath   文件保存路径，包括文件名和扩展名
     */
    public void saveImage(byte[] imageBytes, String filePath) {
        File file = new File(filePath);
        // 如果目标目录不存在，则创建它
        File parentDir = file.getParentFile();
        if (!parentDir.exists() && !parentDir.mkdirs()) {
            System.out.println("无法创建目录：" + parentDir.getAbsolutePath());
            return;
        }
        try (FileOutputStream fos = new FileOutputStream(file)) {
            fos.write(imageBytes);
            System.out.println("图片已成功保存至: " + filePath);
        } catch (IOException e) {
            e.printStackTrace();
            System.out.println("保存图片时发生错误：" + e.getMessage());
        }
    }


    public void saveImageOss(byte[] imageBytes, String filePath) {
        // Endpoint以华东1（杭州）为例，其它Region请按实际情况填写。
        String endpoint = "https://check-order.oss-cn-beijing.aliyuncs.com";
        // 从环境变量中获取访问凭证。运行本代码示例之前，请确保已设置环境变量OSS_ACCESS_KEY_ID和OSS_ACCESS_KEY_SECRET。
        EnvironmentVariableCredentialsProvider credentialsProvider = null;
        try {
            credentialsProvider = CredentialsProviderFactory.newEnvironmentVariableCredentialsProvider();
        } catch (ClientException e) {
            throw new RuntimeException(e);
        }
        // 填写Bucket名称，例如examplebucket。
        String bucketName = "check-order";
        // 填写Object完整路径，完整路径中不能包含Bucket名称，例如exampledir/exampleobject.txt。
        String objectName = "2025/02/26/pic_Media_202502261810271777966936_75252.png";
        // 填写Bucket所在地域。以华东1（杭州）为例，Region填写为cn-hangzhou。
        String region = "cn-beijing";

        // 创建OSSClient实例。
        ClientBuilderConfiguration clientBuilderConfiguration = new ClientBuilderConfiguration();
        clientBuilderConfiguration.setSignatureVersion(SignVersion.V4);
        OSS ossClient = OSSClientBuilder.create()
                .endpoint(endpoint)
                .credentialsProvider(credentialsProvider)
                .clientConfiguration(clientBuilderConfiguration)
                .region(region)
                .build();

        try {
            // 填写Byte数组。
            byte[] content = imageBytes;
            // 创建PutObjectRequest对象。
            PutObjectRequest putObjectRequest = new PutObjectRequest(bucketName, objectName, new ByteArrayInputStream(content));

            // 创建PutObject请求。
            PutObjectResult result = ossClient.putObject(putObjectRequest);
        } catch (OSSException oe) {
            System.out.println("Caught an OSSException, which means your request made it to OSS, "
                    + "but was rejected with an error response for some reason.");
            System.out.println("Error Message:" + oe.getErrorMessage());
            System.out.println("Error Code:" + oe.getErrorCode());
            System.out.println("Request ID:" + oe.getRequestId());
            System.out.println("Host ID:" + oe.getHostId());
        } finally {
            if (ossClient != null) {
                ossClient.shutdown();
            }
        }
    }

}
